#include <QQmlContext>
#include <QQmlProperty>
#include <private/qqmlproperty_p.h>
#include <QCoreApplication>
#include "QQuickROData.h"
#include "ROHelper.h"


ROHelper::ROHelper()
{
    moveToThread(qApp->thread());
}

ROHelper::~ROHelper()
{

}

ROTriggeredUpdater *ROHelper::triggered()
{
    if(!m_triggered)
    {
        m_triggered = new ROTriggeredUpdater(this);
    }

    return m_triggered;
}

ROFramedUpdater *ROHelper::framed()
{
    if(!m_framed)
    {
        m_framed = new ROFramedUpdater(this);
    }

    return m_framed;
}

ROHelper *ROHelper::instance()
{
    static ROHelper i;
    return &i;
}

QObject *ROHelper::createObjectFromComponent(QQmlComponent *comp, const QVariantMap &param)
{
    if(!comp)
    {
        return nullptr;
    }

    auto data = getROObjectData(comp);

    if(!data || !data->host)
    {
        return nullptr;
    }


    auto obj = createObject(comp,nullptr,param);

    if(obj)
    {
        obj->setParent(comp);
        data->host->registerObject(obj,{"direct","comp",QString::number(data->id),QString::number(data->id)});
    }

    return obj;
}

QObject *ROHelper::createObjectFromUrl(QObject *parent, QUrl source, const QVariantMap &param)
{
    auto data = getROObjectData(parent);
    if(!data)
    {
        return nullptr;
    }

    auto context = qmlContext(parent);
    if(!context)
    {
        return nullptr;
    }

    auto engine = context->engine();

    QQmlComponent* comp = nullptr;
    if(!m_comps.contains(source))
    {
        comp = new QQmlComponent(engine,source,this);
        m_comps[source] = comp;
    }
    else{
        comp = m_comps[source];
    }

    auto obj = createObject(comp,nullptr,param);

    if(obj)
    {
        obj->setParent(parent);
        data->host->registerObject(obj,{"direct","url",QString::number(data->id),source.toString()});
    }

    return obj;
}

ROHost *ROHelper::getHost(QObject *obj)
{
    auto data = getROObjectData(obj);

    if(data)
    {
        return data->host;
    }

    return nullptr;
}

RONode *ROHelper::getNode(QObject *obj)
{
    auto data = getROObjectData(obj);

    if(data)
    {
        return data->node;
    }

    return nullptr;
}

void ROHelper::removeBinding(QObject *obj, QString property)
{
    QQmlProperty prop(obj,property);

    QQmlPropertyPrivate::removeBinding(prop);
}
